package user

import (
	"fmt"
	"golang.org/x/crypto/bcrypt"
	"gorm.io/gorm"
	"shop/database/mysql"
	"shop/formdata"
	"shop/internal/server"
	"strconv"
)

type User struct {
	gorm.Model
	Username string `json:"username" gorm:"type:varchar(20);unique;default:NULL"`
	Password string `json:"password" gorm:"type:varchar(255);"`
	Phone    string `json:"phone" gorm:"type:char(11);unique"`
	ImageUrl string `json:"imageUrl" gorm:"type:varchar(255);"`
	Sex      int    `json:"sex" gorm:"type:tinyint(1);comment:性别：1 男，2 女;default:0"`
	Status   int    `json:"status" gorm:"type:int(11);comment:0正常，1退出,6 vip;default:0"`
	Address  string `json:"address" gorm:"type:json;column:address;default:NULL"`
	Birth    string `json:"birth" gorm:"type:varchar(255);column:birth;default:NULL"`
}

func (u *User) UserAdd(phone, pass string) (user *User, err error) {
	return user, mysql.WithMysql(func(db *gorm.DB) error {
		// 1. 密码加密处理
		hashedPassword, err := bcrypt.GenerateFromPassword([]byte(pass), bcrypt.DefaultCost)
		if err != nil {
			return fmt.Errorf("密码加密失败: %v", err)
		}

		// 2. 事务优化
		return db.Transaction(func(tx *gorm.DB) error {
			// 创建用户
			newUser := &User{
				Phone:    phone,
				Password: string(hashedPassword),
				Status:   0,
			}

			if err := tx.Table("users").Create(newUser).Error; err != nil {
				return fmt.Errorf("用户创建失败: %v", err)
			}

			// 3. 获取创建的用户记录
			return tx.Table("users").
				Where("phone = ?", phone).
				First(&user).Error

		})
	})
}

func (u *User) UserSearchByID(userID int) (user User, err error) {
	return user, mysql.WithMysql(func(db *gorm.DB) error {
		return db.Table("users").Where("id = ?", userID).First(&user).Error
	})
}

func (u *User) UserSearchByPhone(phone string) (user User, err error) {
	return user, mysql.WithMysql(func(db *gorm.DB) error {
		return db.Table("users").Where("phone = ?", phone).First(&user).Error
	})
}

// UpdatePassword 修改用户密码
func (u *User) UpdatePassword(phone, password string) (user User, err error) {
	// 使用事务处理数据库操作
	err = mysql.WithMysql(func(db *gorm.DB) error {
		// 1. 密码加密处理
		hashedPassword, err := bcrypt.GenerateFromPassword([]byte(password), bcrypt.DefaultCost)
		if err != nil {
			return fmt.Errorf("密码加密失败: %v", err)
		}
		// 2. 更新密码
		// 通过电话查询用户并更新密码字段
		result := db.Table("users").Where("phone = ?", phone).Update("password", string(hashedPassword))

		// 检查更新是否成功
		if result.Error != nil {
			return fmt.Errorf("密码更新失败: %v", result.Error)
		}
		if result.RowsAffected == 0 {
			return fmt.Errorf("未找到该手机号的用户")
		}
		// 获取更新后的用户信息
		if err := db.Table("users").Where("phone = ?", phone).First(&user).Error; err != nil {
			return fmt.Errorf("查询用户信息失败: %v", err)
		}
		return nil
	})
	// 返回修改后的用户信息
	return user, err
}

func (u *User) UpdatePhone(phone, newPhone string) (user User, err error) {
	// 使用事务处理数据库操作
	err = mysql.WithMysql(func(db *gorm.DB) error {
		// 2. 更新密码
		// 通过电话查询用户并更新密码字段
		result := db.Table("users").Where("phone = ?", phone).Update("phone", newPhone)

		// 检查更新是否成功
		if result.Error != nil {
			return fmt.Errorf("手机号更新失败: %v", result.Error)
		}
		if result.RowsAffected == 0 {
			return fmt.Errorf("未找到该手机号的用户")
		}
		// 获取更新后的用户信息
		if err := db.Table("users").Where("phone = ?", newPhone).First(&user).Error; err != nil {
			return fmt.Errorf("查询用户信息失败: %v", err)
		}
		return nil
	})
	// 返回修改后的用户信息
	return user, err
}

func (u *User) UpdateStatus(userID int) (user User, err error) {
	return user, mysql.WithMysql(func(db *gorm.DB) error {
		// 通过电话查询用户并更新密码字段
		result := db.Table("users").Where("id = ?", userID).Update("status", 1)
		// 检查更新是否成功
		if result.Error != nil {
			return fmt.Errorf("更新失败: %v", result.Error)
		}
		if result.RowsAffected == 0 {
			return fmt.Errorf("未找到该用户")
		}
		// 获取并返回最新数据
		if err = db.Table("users").Where("id = ?", userID).First(&user).Error; err != nil {
			return fmt.Errorf("获取用户数据失败: %v", err)
		}
		return nil
	})
}

func (u *User) UserUpdate(message formdata.UserMessage) (user *User, err error) {
	return user, mysql.WithMysql(func(db *gorm.DB) error {
		token, _ := server.GetToken(message.Token)
		UserID, _ := strconv.Atoi(token)

		// 创建更新对象
		user = &User{
			Model:    gorm.Model{ID: uint(UserID)},
			Username: message.Nickname,
			ImageUrl: message.Img,
			Sex:      message.Sex,
			Birth:    message.Birth,
		}

		// 通过用户ID更新数据
		result := db.Table("users").Where("id = ?", UserID).Updates(map[string]interface{}{
			"username":  message.Nickname,
			"image_url": message.Img,
			"sex":       message.Sex,
			"birth":     message.Birth,
		})

		// 错误处理
		if result.Error != nil {
			return fmt.Errorf("用户数据更新失败: %v", result.Error)
		}
		if result.RowsAffected == 0 {
			return fmt.Errorf("未找到该用户")
		}

		// 获取并返回最新数据
		if err := db.Table("users").Where("id = ?", UserID).First(&user).Error; err != nil {
			return fmt.Errorf("获取用户数据失败: %v", err)
		}

		return nil
	})
}
